home *** CD-ROM | disk | FTP | other *** search
/ Mac Easy 2010 May / Mac Life Ubuntu.iso / casper / filesystem.squashfs / usr / src / linux-headers-2.6.28-15 / scripts / export_report.pl < prev    next >
Encoding:
Perl Script  |  2008-12-24  |  4.2 KB  |  170 lines

  1. #!/usr/bin/perl -w
  2. #
  3. # (C) Copyright IBM Corporation 2006.
  4. #    Released under GPL v2.
  5. #    Author : Ram Pai (linuxram@us.ibm.com)
  6. #
  7. # Usage: export_report.pl -k Module.symvers [-o report_file ] -f *.mod.c
  8. #
  9.  
  10. use Getopt::Std;
  11. use strict;
  12.  
  13. sub numerically {
  14.     my $no1 = (split /\s+/, $a)[1];
  15.     my $no2 = (split /\s+/, $b)[1];
  16.     return $no1 <=> $no2;
  17. }
  18.  
  19. sub alphabetically {
  20.     my ($module1, $value1) = @{$a};
  21.     my ($module2, $value2) = @{$b};
  22.     return $value1 <=> $value2 || $module2 cmp $module1;
  23. }
  24.  
  25. sub print_depends_on {
  26.     my ($href) = @_;
  27.     print "\n";
  28.     while (my ($mod, $list) = each %$href) {
  29.         print "\t$mod:\n";
  30.         foreach my $sym (sort numerically @{$list}) {
  31.             my ($symbol, $no) = split /\s+/, $sym;
  32.             printf("\t\t%-25s\t%-25d\n", $symbol, $no);
  33.         }
  34.         print "\n";
  35.     }
  36.     print "\n";
  37.     print "~"x80 , "\n";
  38. }
  39.  
  40. sub usage {
  41.         print "Usage: @_ -h -k Module.symvers  [ -o outputfile ] \n",
  42.           "\t-f: treat all the non-option argument as .mod.c files. ",
  43.           "Recommend using this as the last option\n",
  44.           "\t-h: print detailed help\n",
  45.           "\t-k: the path to Module.symvers file. By default uses ",
  46.           "the file from the current directory\n",
  47.           "\t-o outputfile: output the report to outputfile\n";
  48.     exit 0;
  49. }
  50.  
  51. sub collectcfiles {
  52.         my @file = `cat .tmp_versions/*.mod | grep '.*\.ko\$'`;
  53.         @file = grep {s/\.ko/.mod.c/} @file;
  54.     chomp @file;
  55.         return @file;
  56. }
  57.  
  58. my (%SYMBOL, %MODULE, %opt, @allcfiles);
  59.  
  60. if (not getopts('hk:o:f',\%opt) or defined $opt{'h'}) {
  61.         usage($0);
  62. }
  63.  
  64. if (defined $opt{'f'}) {
  65.     @allcfiles = @ARGV;
  66. } else {
  67.     @allcfiles = collectcfiles();
  68. }
  69.  
  70. if (not defined $opt{'k'}) {
  71.     $opt{'k'} = "Module.symvers";
  72. }
  73.  
  74. unless (open(MODULE_SYMVERS, $opt{'k'})) {
  75.     die "Sorry, cannot open $opt{'k'}: $!\n";
  76. }
  77.  
  78. if (defined $opt{'o'}) {
  79.     unless (open(OUTPUT_HANDLE, ">$opt{'o'}")) {
  80.         die "Sorry, cannot open $opt{'o'} $!\n";
  81.     }
  82.     select OUTPUT_HANDLE;
  83. }
  84. #
  85. # collect all the symbols and their attributes from the
  86. # Module.symvers file
  87. #
  88. while ( <MODULE_SYMVERS> ) {
  89.     chomp;
  90.     my (undef, $symbol, $module, $gpl) = split;
  91.     $SYMBOL { $symbol } =  [ $module , "0" , $symbol, $gpl];
  92. }
  93. close(MODULE_SYMVERS);
  94.  
  95. #
  96. # collect the usage count of each symbol.
  97. #
  98. foreach my $thismod (@allcfiles) {
  99.     unless (open(MODULE_MODULE, $thismod)) {
  100.         print "Sorry, cannot open $thismod: $!\n";
  101.         next;
  102.     }
  103.     my $state=0;
  104.     while ( <MODULE_MODULE> ) {
  105.         chomp;
  106.         if ($state == 0) {
  107.             $state = 1 if ($_ =~ /static const struct modversion_info/);
  108.             next;
  109.         }
  110.         if ($state == 1) {
  111.             $state = 2 if ($_ =~ /__attribute__\(\(section\("__versions"\)\)\)/);
  112.             next;
  113.         }
  114.         if ($state == 2) {
  115.             if ( $_ !~ /0x[0-9a-f]+,/ ) {
  116.                 next;
  117.             }
  118.             my $sym = (split /([,"])/,)[4];
  119.             my ($module, $value, $symbol, $gpl) = @{$SYMBOL{$sym}};
  120.             $SYMBOL{ $sym } =  [ $module, $value+1, $symbol, $gpl];
  121.             push(@{$MODULE{$thismod}} , $sym);
  122.         }
  123.     }
  124.     if ($state != 2) {
  125.         print "WARNING:$thismod is not built with CONFIG_MODVERSION enabled\n";
  126.     }
  127.     close(MODULE_MODULE);
  128. }
  129.  
  130. print "\tThis file reports the exported symbols usage patterns by in-tree\n",
  131.     "\t\t\t\tmodules\n";
  132. printf("%s\n\n\n","x"x80);
  133. printf("\t\t\t\tINDEX\n\n\n");
  134. printf("SECTION 1: Usage counts of all exported symbols\n");
  135. printf("SECTION 2: List of modules and the exported symbols they use\n");
  136. printf("%s\n\n\n","x"x80);
  137. printf("SECTION 1:\tThe exported symbols and their usage count\n\n");
  138. printf("%-25s\t%-25s\t%-5s\t%-25s\n", "Symbol", "Module", "Usage count",
  139.     "export type");
  140.  
  141. #
  142. # print the list of unused exported symbols
  143. #
  144. foreach my $list (sort alphabetically values(%SYMBOL)) {
  145.     my ($module, $value, $symbol, $gpl) = @{$list};
  146.     printf("%-25s\t%-25s\t%-10s\t", $symbol, $module, $value);
  147.     if (defined $gpl) {
  148.         printf("%-25s\n",$gpl);
  149.     } else {
  150.         printf("\n");
  151.     }
  152. }
  153. printf("%s\n\n\n","x"x80);
  154.  
  155. printf("SECTION 2:\n\tThis section reports export-symbol-usage of in-kernel
  156. modules. Each module lists the modules, and the symbols from that module that
  157. it uses.  Each listed symbol reports the number of modules using it\n");
  158.  
  159. print "~"x80 , "\n";
  160. while (my ($thismod, $list) = each %MODULE) {
  161.     my %depends;
  162.     $thismod =~ s/\.mod\.c/.ko/;
  163.     print "\t\t\t$thismod\n";
  164.     foreach my $symbol (@{$list}) {
  165.         my ($module, $value, undef, $gpl) = @{$SYMBOL{$symbol}};
  166.         push (@{$depends{"$module"}}, "$symbol $value");
  167.     }
  168.     print_depends_on(\%depends);
  169. }
  170.